import { useState, useEffect, useRef, useMemo } from 'react';
import { message, Tabs } from 'antd';
import clsx from 'clsx';
import type { Application } from '@/canvas';
import Icon from '@/components/Icon';
import Collapse from '@/components/Collapse';
import { styleList, textureList, partList, materialList } from '../config';
import styles from './index.module.scss';
import { ArrowLeftOutlined } from '@ant-design/icons';

interface IRighter {
  app: Application;
  setLoading: (loading: boolean) => void;
}

export default ({ app, setLoading }: IRighter) => {
  const [tabKey, setTabKey] = useState<'guiti' | 'chouti' | ''>('');
  const [colKeys, setColKeys] = useState<string[]>(['0']);
  const [style, setStyle] = useState<number>(0);
  const [texture, setTexture] = useState<number>(0);
  const [parts, setParts] = useState<(number | undefined)[]>([]);
  const [partNodes, setPartNodes] = useState<any[]>([]);
  const [material, setMaterial] = useState<number>(0);


  const [guitiTab, setGuitiTab] = useState<'guitistyle' | 'guitihuase'>("guitistyle");
  const [choutiTab, setChoutiTab] = useState<string>("一层");

  const ref = useRef<any>();
  const divRef = useRef<any>();

  // 切换柜子
  const initModel = async () => {
    const current = styleList[style];

    setLoading(true);

    ref.current = await app.addCabint({
      url: current.url,
      partsTexture: current.textures
    });

    setLoading(false);
  }

  // 删除配件
  const removeParts = (layer?: number) => {
    if (partNodes.length < 1) return;

    for (let i = 0; i < partNodes.length; i++) {
      if ((layer === undefined || layer === i) && partNodes[i] !== undefined) {
        app.removeModel(partNodes[i]);
      }
    }

    setPartNodes([]);
  }

  // 调整抽屉中物体的位置
  const adjustPartPos = (node: any, index: number) => {
    let origin = { x: 0, y: -0.025 };
    if (app.isOpen(index)) {
      origin = { x: 0, y: 0.575 };
    }
    node.position.x = origin.x;
    node.position.z = origin.y;
    node.visible = true;
  }



  useEffect(() => {
    initModel();
  }, [style]);

  const onTabClick = (key: 'guiti' | 'chouti' | '') => {
    setTabKey(key);
  }


  const onModelChange = async (field: string, value: number, layer: number) => {
    const node = ref.current;

    if (app.isRuning()) {
      return message.warning('开门动画未结束');
    }

    if (field === 'style') {
      removeParts();

      setColKeys(['0']);
      setStyle(value);
      setTexture(0);
      setParts([]);
      setMaterial(0);
      setChoutiTab('一层');
    } else if (field === 'texture') {
      const guitiKeys = styleList[style].guitiKeys;
      const textureUrl = textureList[value].url;

      app.replaceBatchMaterial(node, guitiKeys.map(key => ({
        name: key,
        url: textureUrl
      })));
      setTexture(value);
    } else if (field === 'part') {
      removeParts(layer);

      const partUrl = partList[value].url;
      const partkeys = partList[value].mkeys;
      const materialUrl = materialList[material].url;

      const ys = style < 1 ? [-0.22, 0.03, 0.27] : [-0.22, 0.16];
      const choutiNum = style < 1 ? 3 : 2;

      const pn = await app.addPart({
        url: partUrl,
        partsTexture: partkeys.map(n => ({ name: n, url: materialUrl }))
      });

      pn.position.x = 0;
      pn.position.y = ys[(choutiNum - 1) - layer];
      pn.position.z = 0;
      pn.name = `part0${choutiNum - layer}`;

      const [np, nn]: any[][] = [[], []];
      for (let i = 0; i < ys.length; i++) {
        if (i === layer) {
          np[i] = value;
          nn[i] = pn;
        } else {
          np[i] = parts[i];
          nn[i] = partNodes[i];
        }
      }

      adjustPartPos(pn, (choutiNum - 1) - layer);
      setParts(np);
      setPartNodes(nn);
    } else if (field === 'material') {
      if (parts.every(n => n === undefined) || partNodes.every(n => n === undefined)) return;

      const materialUrl = materialList[value].url;

      for (let i = 0; i < partNodes.length; i++) {
        if (partNodes[i] !== undefined && parts[i] !== undefined) {
          const partkeys = partList[parts[i]!].mkeys;

          app.replaceBatchMaterial(partNodes[i], partkeys.map(key => ({
            name: key,
            url: materialUrl
          })));
        }
      }

      setMaterial(value);
    }
  }

  // 抽屉组件
  const partItems = useMemo(() => {
    const labels = ['一层', '二层'];

    if (style < 1) {
      labels.push('三层');
    }

    labels.push("花色");
    return <div className={styles.choutiBox}>
      <div className={styles.header}>
        <div className={styles.back} onClick={() => {
          onTabClick('');
        }}>
          <ArrowLeftOutlined />
        </div>
        <div className={styles.list}>
          {
            labels.map((e: string) => {
              return <div key={e} className={clsx(styles.item, choutiTab === e ? styles.ac : "")} onClick={() => {
                setChoutiTab(e);
              }}>{e}</div>
            })
          }
        </div>
      </div>
      {
        labels.slice(0, -1).map((str, cdx) => {
          return <div className={styles.content} key={cdx} style={{display: choutiTab === str ? "" : "none"}}>
            {partList.map((item, idx) => (
              <div
                className={clsx(styles.rect, parts[cdx] === idx && styles.ac)}
                onClick={() => onModelChange('part', idx, cdx)}
                key={item.key}
              >
                <img className={styles.lt} src={item.thumb} alt={item.name} />
                <div className={styles.ct}>
                  <div className={styles.name}>
                    {item.name}
                  </div>
                </div>
                {/* <div className={styles.rg}>
                  <div className={styles.price}>¥ {item.price}</div>
                  <Icon className={styles.check} type="success-filling" />
                </div> */}
              </div>
            ))}
          </div>
        })
      }
      {
        choutiTab === "花色" ? <div className={styles.content}>
          {materialList.map((item, idx) => (
            <div
              className={clsx(styles.circle, material === idx && styles.ac)}
              onClick={() => onModelChange('material', idx, 0)}
              key={item.key}
            >
              <div className={styles.imgBox}>
                <img src={item.url} alt={item.name} />
              </div>

              <div className={styles.name}>
                颜色{['一', '二', '三', '四', '五', '六', '七'][idx]}
              </div>
            </div>
          ))}
        </div> : null
      }
    </div>
  }, [style, parts, choutiTab, material]);

  return (
    <div className={styles.modelConfig}>
      {
        !tabKey ? <div className={styles.tabs}>
          <div className={clsx(styles.tab)} onClick={() => {
            onTabClick("guiti");
          }}>
            <div className={clsx(styles.icon, styles.guiti)}></div>
            <div className={clsx(styles.title)}>外观</div>
          </div>
          <div className={clsx(styles.tab)} onClick={() => {
            onTabClick("chouti");
          }}>
            <div className={clsx(styles.icon, styles.chouti)}></div>
            <div className={clsx(styles.title)}>抽屉</div>
          </div>
        </div> : null
      }
      {
        tabKey == "guiti" ? <div className={styles.guitiBox}>
          <div className={styles.header}>
            <div className={styles.back} onClick={() => {
              onTabClick('');
            }}>
              <ArrowLeftOutlined />
            </div>
            <div className={styles.list}>
              <div className={clsx(styles.item, guitiTab === "guitistyle" ? styles.ac : "")} onClick={() => {
                setGuitiTab('guitistyle');
              }}>样式</div>
              <div className={clsx(styles.item, guitiTab === "guitihuase" ? styles.ac : "")} onClick={() => {
                setGuitiTab('guitihuase');
              }}>花色</div>
            </div>
          </div>
          {
            guitiTab === 'guitistyle' ? <div className={styles.content}>
              {styleList.map((item, idx) => (
                <div
                  className={clsx(styles.rect, style === idx && styles.ac)}
                  onClick={() => onModelChange('style', idx, 0)}
                  key={item.key}
                >
                  <img className={styles.lt} src={item.thumb} alt={item.name} />
                  <div className={styles.ct}>
                    <div className={styles.name}>
                      {item.name}
                    </div>
                  </div>
                  {/* <div className={styles.rg}>
                    <div className={styles.price}>¥ {item.price}</div>
                    <Icon className={styles.check} type="success-filling" />
                  </div> */}
                </div>
              ))}
            </div> :
              <div className={styles.content}>
                {textureList.map((item, idx) => (
                  <div
                    className={clsx(styles.circle, texture === idx && styles.ac)}
                    onClick={() => onModelChange('texture', idx, 0)}
                    key={item.key}
                  >
                    <div className={styles.imgBox}>
                      <img src={item.url} alt={item.name} />
                    </div>

                    <div className={styles.name}>
                      颜色{['一', '二'][idx]}
                    </div>
                  </div>
                ))}
              </div>
          }
        </div> : null
      }
      {
        tabKey == "chouti" ? partItems : null
      }
    </div>
  );
};
